<?php

namespace App\Repository;

use App\Entity\PageCategory;
use App\Enum\RedisKeyEnum;
use App\Service\Redis;
use Doctrine\Bundle\DoctrineBundle\Repository\ServiceEntityRepository;
use Doctrine\Persistence\ManagerRegistry;
use Symfony\Component\Security\Core\Security;

/**
 * @method PageCategory|null find($id, $lockMode = null, $lockVersion = null)
 * @method PageCategory|null findOneBy(array $criteria, array $orderBy = null)
 * @method PageCategory[]    findAll()
 * @method PageCategory[]    findBy(array $criteria, array $orderBy = null, $limit = null, $offset = null)
 */
class PageCategoryRepository extends ServiceEntityRepository {
    private $redis;
    private $security;

    public function __construct (ManagerRegistry $registry, Redis $redis, Security $security) {
        parent::__construct($registry, PageCategory::class);
        $this->redis = $redis->redis;
        $this->security = $security;
    }

    /**
     * 获取类别数据(缓存)
     * @return array|mixed
     */
    public function findAllToArray () {
        $result = [];

        $redis_key = RedisKeyEnum::REDIS_PAGE_CATEGORY_FIND_ALL_BY_ARRAY_KEY;
        $redis_page_category_data = $this->redis->get($redis_key);
        if (is_null($redis_page_category_data)) {
            $objs = $this->findAll();
            foreach ($objs as $obj) {
                $result[$obj->getId()] = $obj->getValue();
            }
            $this->redis->setex($redis_key, 600, serialize($result));
        } else {
            $result = unserialize($redis_page_category_data);
        }

        return $result;
    }

    /**
     * 更新缓存
     */
    public function updateCache () {
        $result = [];
        $redis_key = RedisKeyEnum::REDIS_PAGE_CATEGORY_FIND_ALL_BY_ARRAY_KEY;
        $objs = $this->findAll();
        foreach ($objs as $obj) {
            $result[$obj->getId()] = $obj->getValue();
        }
        $this->redis->setex($redis_key, 600, serialize($result));
    }

    /**
     * 热门类别
     * @param bool $is_auth
     * @return mixed[]
     * @throws \Doctrine\DBAL\Driver\Exception
     * @throws \Doctrine\DBAL\Exception
     */
    public function getTopCategory ($is_auth = false) {
        $conn = $this->getEntityManager()->getConnection();
        $sql = 'SELECT c.id, c.value, count(p.id) as num
                from page as p
                left join page_category as c on p.page_category_id = c.id 
                where p.status = 1 ';
        if ($is_auth) {
            if (!$this->security->getUser()->isSuperAdmin()) {
                $sql .= ' and p.admin_user_id = '.$this->security->getUser()->getId().' ';
            }
        }
        $sql .= 'GROUP BY p.page_category_id';

        $stmt = $conn->prepare($sql);
        $stmt->execute();
        return $stmt->fetchAllAssociative();
    }
}
